using System.Collections.Generic;
using System.Data;
using TestSystem.DAL.TestSystem;

namespace TestSystem.BLL.TestSystem
{
    public class Subject : BusinessEntity
    {
        #region private fields
        private int _subjectID;
        private string _subjectName;
        private string _description;
        private bool _deleted;
        #endregion

        #region public props and methods
        public int SubjectID
        {
            get { return _subjectID; }
            set { _subjectID = value; }
        }

        public string SubjectName
        {
            get { return _subjectName; }
            set { _subjectName = value; }
        }

        public string Description
        {
            get { return _description; }
            set { _description = value; }
        }

        public bool Deleted
        {
            get { return _deleted; }
            set { _deleted = value; }
        }

        private List<Quiz> _quizes = null;
        public List<Quiz> Quizes
        {
            get
            {
                if(_quizes == null)
                    _quizes = Quiz.GetBySubjectID(this.SubjectID);
                return _quizes;
            }
        }

        public override void Update()
        {
            SubjectDataAccess.UpdateSubject(this.SubjectID, this.SubjectName, this.Description, this.Deleted);
        }

        public int AddQuiz(string title, string description, int questionsCount, bool useTimer, int timePerQuiz, int scoreToPass, bool active, bool saveUserAnswers, int maxScores, string levelsPercentage)
        {
            if (Utils.CurrentUser.Identity.IsAuthenticated)
            {
                string addedBy = Utils.CurrentUser.Identity.Name;
                return Quiz.Add(title, description, SubjectID, addedBy, questionsCount, useTimer, timePerQuiz, scoreToPass, active, saveUserAnswers, maxScores, levelsPercentage);
            }
            return -1;
        }

        public void RemoveQuizes()
        {
            Quiz.RemoveBySubjectID(this.SubjectID);
            _quizes = null;
        }

        private int _quizesCount = 0;
        public int QuizesCount
        {
            get
            {
                if (_quizesCount == 0)
                    _quizesCount = Quiz.GetCountBySubjectID(this.SubjectID);
                return _quizesCount;
            }
        }

        protected override void Load(IDataReader rdr)
        {
            SubjectID = (int) rdr["SubjectID"];
            SubjectName = SubjectDataAccess.FromDBValue<string>(rdr["SubjectName"]);
            Description = SubjectDataAccess.FromDBValue<string>(rdr["Description"]);
            Deleted = (bool) rdr["Deleted"];
        }
        #endregion

        #region static methods
        public static int Add(string subjectName, string description)
        {
            return SubjectDataAccess.InsertSubject(subjectName, description);
        }
        
        public static List<Subject> GetAll(bool selectDeleted)
        {
            return GetAll(selectDeleted, -1);
        }

        public static List<Subject> GetAll(bool selectDeleted, int pageIndex)
        {
            if (pageIndex == -1)
                return LoadList<Subject>(SubjectDataAccess.GetAll(selectDeleted, -1, -1));
            int pageSize = 20; // subjects per one page
            int lowerBound = (pageIndex*pageSize) + 1;
            int upperBound = (pageIndex + 1)*pageSize;
            return LoadList<Subject>(SubjectDataAccess.GetAll(selectDeleted, lowerBound, upperBound));
        }

        public static List<Subject> GetAll(int startRowIndex, int maximumRows)
        {
            int pageIndex = PageIndex(startRowIndex, maximumRows);
            int pageSize = 20; // subjects per one page
            int lowerBound = (pageIndex * pageSize) + 1;
            int upperBound = (pageIndex + 1) * pageSize;
            return LoadList<Subject>(SubjectDataAccess.GetAll(true, lowerBound, upperBound));
        }

        public static Subject GetBySubjectID(int subjectID)
        {
            return LoadEntity<Subject>(SubjectDataAccess.GetBySubjectID(subjectID));
        }

        public static void Remove(int subjectID)
        {
            SubjectDataAccess.DeleteSubject(subjectID);
        }
        
        public static int GetCount()
        {
            return SubjectDataAccess.GetCount();
        }
        #endregion
    }
}
